package com.lms.service.impl;

import com.lms.bean.Book;
import com.lms.bean.Request;
import com.lms.bean.User;
import com.lms.dao.RequestDao;
import com.lms.service.RequestService;
import com.lms.util.MyStringUtils;
import com.lms.util.QueryResult;
import com.lms.vo.RequestVO;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.thymeleaf.util.StringUtils;

import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Predicate;
import javax.persistence.criteria.Root;
import java.util.ArrayList;
import java.util.List;

@Service
public class RequestServiceImpl implements RequestService {
    @Autowired
    private RequestDao requestDao;

    @Override
    public void save(Request request) {
        System.out.println("request = " + request);
        requestDao.save(request);
    }

    @Override
    public Page<Request> findAll(Pageable pageable) {
        Page<Request> page = requestDao.findAll(pageable);
        List<Request> content = page.getContent();
        for (Request request : content) {
            RequestVO.parse(request);
        }
        return page;
    }

    @Override
    public Request findRequestById(Long requestId) {
        return requestDao.findById(requestId).orElse(null);
    }

    @Override
    public QueryResult<RequestVO> queryByKeyWordLike(int page, int pageSize, String keyword) {
        Sort sort = Sort.by(Sort.Direction.DESC, "createTime");
        Pageable pageable = PageRequest.of(page, pageSize, sort);

        Specification<Request> specification = new Specification<Request>() {
            @Override
            public Predicate toPredicate(Root<Request> root, CriteriaQuery<?> criteriaQuery, CriteriaBuilder criteriaBuilder) {
                List<Predicate> predicates = new ArrayList<>();
                predicates.add(criteriaBuilder.like(root.<User>get("user").get("username"), "%" + keyword + "%"));
                predicates.add(criteriaBuilder.like(root.<Book>get("book").get("bookName"), "%" + keyword + "%"));
                Predicate[] p1 = new Predicate[predicates.size()];
                Predicate predicate = criteriaBuilder.or(predicates.toArray(p1));
                criteriaQuery.where(predicate);
                return null;
            }
        };

        Page<Request> p = requestDao.findAll(specification, pageable);

        List<Request> list = p.getContent();
        List<RequestVO> requestVOList = new ArrayList<>();
        list.forEach(request ->requestVOList.add(RequestVO.convert(request)));

        QueryResult<RequestVO> queryResult = new QueryResult<>();
        queryResult.setTotalCount(p.getTotalElements());
        queryResult.setData(requestVOList);

        return queryResult;
    }

    @Override
    public Page<Request> findAll(Pageable pageable, Long userId) {

        Specification<Request> specification = new Specification<Request>() {
            @Override
            public Predicate toPredicate(Root<Request> root, CriteriaQuery<?> criteriaQuery, CriteriaBuilder criteriaBuilder) {
                Predicate predicate = criteriaBuilder.equal(root.get("user").get("userId"),userId);
                criteriaQuery.where(predicate);
                return null;
            }
        };
        Page<Request> page = requestDao.findAll(specification,pageable);
        List<Request> content = page.getContent();
        for (Request request : content) {
            RequestVO.parse(request);
        }
        return page;
    }

    @Override
    public Long findAllNoHandleCount() {
        return (long)requestDao.findAll((root, criteriaQuery,  criteriaBuilder)->{
            Predicate predicate = criteriaBuilder.equal(root.get("handleCode"),0);
            criteriaQuery.where(predicate);
            return null;
        }).size();
    }

    @Override
    public void deleteById(Long id) {
        try {
            requestDao.deleteById(id);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    @Override
    public void deleteAll(String ids) {
        String[] split = ids.split(",");
        for (String s : split) {
            if(MyStringUtils.isNumeric(s)){
                requestDao.deleteById(Long.parseLong(s));
            }
        }

    }

}
